package com.mnb.beidou.service;

import com.mnb.beidou.model.DataEntity;
import com.mnb.beidou.model.ModbusDataEntity;
import com.mnb.beidou.utils.ByteUtils;
import com.mnb.beidou.utils.CRC16Utils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

import java.util.Arrays;

@Component
public class ModbusParser {

    @Autowired
    private Data2CParser data2CParser;

    public ModbusDataEntity parse(String hexMessage) throws Exception {
        hexMessage = hexMessage.replace(" ", "");

        ModbusDataEntity entity = new ModbusDataEntity();

        byte[] data = ByteUtils.hexStringToByteArray(hexMessage);
        int offset = 0;

        // 1. 从机地址（1字节）
        int slaveAddr = data[offset++] & 0xFF;
        entity.setSlaveAddr(String.format("%02X", slaveAddr));

        // 2. 功能码（1字节）
        byte funcCode = data[offset++];
        entity.setFuncCode(String.format("%02X", funcCode));

        // 3. 数据长度（2字节，高字节在前）
        int dataLength = ((data[offset] & 0xFF) << 8) | (data[offset + 1] & 0xFF);
        offset += 2;
        entity.setDataLength(dataLength);

        // 4. 数据部分（以十六进制格式打印）
        // 提取数据部分字节数组
        byte[] dataContent = Arrays.copyOfRange(data, offset, offset + dataLength);
        entity.setDataContent(ByteUtils.bytesToHex(dataContent));

        // 5. CRC校验（2字节）
        boolean isValid = CRC16Utils.validateCRC16(hexMessage);
        if (!isValid) {
            throw new Exception("CRC校验失败");
        }

        DataEntity parse = new DataEntity();
        if (String.format("%02X", funcCode).equals("2C")) {
            parse = data2CParser.parse(ByteUtils.bytesToHex(dataContent));
        }

        entity.setDataEntity(parse);
        return entity;
    }


    public static void main(String[] args) {
        try {
            // 示例报文（来自文档1中的数据）
            String message = "652C003E00000000000000000000000000040000048A00000B9E0000079E00001F1C000000000000000000000000058100006C0000000000000000000000000000004CB7";
            byte[] data = ByteUtils.hexStringToByteArray(message);
            int offset = 0;

            // 1. 从机地址（1字节）
            int slaveAddr = data[offset++] & 0xFF;
            System.out.println("从机地址：" + slaveAddr);

            // 2. 功能码（1字节）
            byte funcCode = data[offset++];
            if (funcCode != 0x2C) {
                System.out.println("错误：功能码不是0x2C，实际为0x" + String.format("%02X", funcCode));
                return;
            }
            System.out.println("功能码：0x" + String.format("%02X", funcCode) + "（主动上报数据）");

            // 3. 数据长度（2字节，高字节在前）
            int dataLength = ((data[offset] & 0xFF) << 8) | (data[offset + 1] & 0xFF);
            offset += 2;
            System.out.println("数据长度：" + dataLength + "字节");

            // 验证数据长度是否匹配
            if (dataLength + 4 != data.length) { // 4 = 从机地址(1) + 功能码(1) + 数据长度(2)
                System.out.println("警告：数据长度不匹配，报文中定义的长度为" + dataLength +
                        "字节，实际数据部分长度为" + (data.length - 4) + "字节");
            }

            // 4. 数据部分（以十六进制格式打印）
            System.out.println("\n数据部分（十六进制）：");
            // 提取数据部分字节数组
            byte[] dataContent = Arrays.copyOfRange(data, offset, offset + dataLength);
            // 打印完整数据内容（十六进制）
            System.out.println("完整数据: " + ByteUtils.bytesToHex(dataContent));

            // 5. CRC校验（2字节）
            if (offset + 1 >= data.length) {
                System.out.println("\n错误：CRC校验位缺失");
                return;
            }
            boolean isValid = CRC16Utils.validateCRC16(message);
            Data2CParser parser = new Data2CParser();
            DataEntity entity = parser.parse(message);

            System.out.println(entity.toString());
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}
